<script setup lang="ts">
import { ref, onBeforeMount, onMounted, h } from 'vue'
import { message } from 'ant-design-vue'
import useRouteList, { actionKeys } from './routeList'
import { listToTree, setTableHeight,sortTreeArr} from '@/common/utils'
//import searchPanel from '@/components/SearchPanel'
import {layoutRouteName} from "@/router/config"
import tableColSetting from '@/components/tableColsSetting/tableColsSetting.vue'
import Add from './add.vue'
import Update from './update.vue'
import { primaryColor_hex } from '@/theme/config'
import { useResizeLR } from '@/hooks/useResizeLR'
import { useTableMixin } from '@/hooks/useTableMixin'

const columns = ref<TableColConfig[]>([
	{
		title: '路由名',
		dataIndex: 'name',
		key: 'name',
		width: 120,
		align: 'center',
	},
	{
		title: '组件路径',
		dataIndex: 'component',
		key: 'component',
		width: 150,
		// align:'center',
		ellipsis: true,
	},
	{
		title: '父级路由标题',
		dataIndex: 'pTitle',
		key: 'pTitle',
		width: 100,
		align: 'center',
	},
	{
		title: 'meta',
		dataIndex: 'meta',
		key: 'meta',
		children: [
			{
				title: '页面标题',
				dataIndex: 'title',
				key: 'title',
				width: 150,
				align: 'center',
			},
			{
				title: '菜单图标',
				dataIndex: 'icon',
				key: 'icon',
				width: 150,
				align: 'center',
			},
			{
				title: '一级菜单的排序序号',
				dataIndex: 'rank',
				key: 'rank',
				width: 150,
				align: 'center',
			},
			{
				title: '是否需要权限访问',
				dataIndex: 'noNeedAuth',
				key: 'noNeedAuth',
				width: 150,
				align: 'center',
				// customRender: ({ text: v }: { text: boolean }) => {
				// 	return v ? '否' : '是'
				// },
				customRender: ({ text: v }: { text: boolean }) => {
					return v ? h('span', { style: { color: 'rgb(245, 108, 108)' } }, '否') : h('span', { style: { color: 'rgb(29, 165, 122)' } }, '是')
				},
			},
			{
				title: '是否缓存',
				dataIndex: 'noKeepAlive',
				key: 'noKeepAlive',
				width: 100,
				align: 'center',
				customRender: ({ text: v }: { text: boolean }) => {
					return v ? '否' : '是'
				},
			},
			{
				title: '是否存在菜单中',
				dataIndex: 'onInMenu',
				key: 'noInMenu',
				width: 120,
				align: 'center',
				customRender: ({ text: v }: { text: boolean }) => {
					return v ? '否' : '是'
				},
			},
			{
				title: '是否隐藏菜单',
				dataIndex: 'hiddenMenu',
				key: 'hiddenMenu',
				width: 100,
				align: 'center',
				customRender: ({ text: v }: { text: boolean }) => {
					return v ? '是' : '否'
				},
			},
			{
				title: '是否隐藏布局',
				dataIndex: 'hiddenLayout',
				key: 'hiddenLayout',
				width: 100,
				align: 'center',
				customRender: ({ text: v }: { text: boolean }) => {
					return v ? '是' : '否'
				},
			},
			{
				title: '是否固定tab页',
				dataIndex: 'affix',
				key: 'affix',
				width: 120,
				align: 'center',
				customRender: ({ text: v }: { text: boolean }) => {
					return v ? '是' : '否'
				},
			},
			{
				title: '是否跳往外部链接',
				dataIndex: 'link',
				key: 'link',
				width: 135,
				align: 'center',
				customRender: (scope: any) => {
					return scope.text ? '是' : '否'
				},
			},
		],
	},
	{
		title: '操作',
		key: 'operation',
		fixed: 'right',
		align: 'center',
		disabled:true,
		// width: 125,  // 如果是动态列宽的话不能给宽度，否则在出现横向滚动条时会有个占位
	},
])
const fixedColWidth = ref<string | number>('0px')
const treeHeight = ref<number>()
const treeData = ref<routeTreeNode[]>([])
const expandedKeys = ref<string[]>([layoutRouteName])
const selectedKeys = ref<string[]>([])
const hasChildKeys=ref<Set<string>>(new Set([]))
const selectedNode = ref({} as routeTreeNode)
const searchOptions = ref<searchOptionType[]>([
	{ type: 'input', id: 'name', props: { label: '路由名' } },
	{ type: 'input', id: 'component', props: { label: '组件路径' } },
	{ type: 'input', id: 'pTitle', props: { label: '父路由标题' } },
	{ type: 'input', id: 'title', props: { label: '路由标题' } },
	{
		type: 'select',
		id: 'noNeedAuth',
		props: { label: '是否需要权限访问' },
		innerComponentProps: {
			filterable: true,
			options: [
				{ label: '是', value: 0, disabled: false },
				{ label: '否', value: 1, disabled: false },
			],
		},
	},
	{
		type: 'select',
		id: 'onInMenu',
		props: { label: '是否存在在菜单' },
		innerComponentProps: {
			filterable: true,
			options: [
				{ label: '是', value: 0, disabled: false },
				{ label: '否', value: 1, disabled: false },
			],
		},
	},
	{
		type: 'select',
		id: 'noKeepAlive',
		props: { label: '是否缓存' },
		innerComponentProps: {
			filterable: true,
			options: [
				{ label: '是', value: 0, disabled: false },
				{ label: '否', value: 1, disabled: false },
			],
		},
	},
])

const routeList = useRouteList()

useResizeLR({
	containerSelector: '.routeManage .container',
	leftBoxSelector: '.routeManage .container .left',
	moveBarSelector: '.routeManage .container .bar',
	rightBoxSelector: '.routeManage .container .right',
	//  lMinW:180,
	rMinW: 800,
	innerMarginW:10,
})


const {
	  current,     // 当前页码
    size,     // 页尺寸
    total,        // 总条数
    filterOptions,  // 查询条件
    getData,        // 获取页数据的方法
    tableHeight,  // 表格高度
    addModalVisible, //新增对话框显示隐藏状态
    updateModalVisible, //更新对话框显示隐藏状态
    tableList,   // 表格数据
    editRow,    // 当前编辑数据
    handleSearchPanelcollapsed,  //search-panel组件的 @collapsed 的处理函数
    handleSearch,   // 搜索处理函数
    handleReset,   // 重置表格数据处理函数
    handlePaginationChange,  // 处理分页器变化处理函数
    handleColumnsChange,    // 表头变化组件的处理函数
    handleAdd,     // 点击新增按钮回调
    handleUpdate,   // 点击更新按钮回调
    handleDelete,   // 删除处理函数
    hanldeAddModalClose,   // 新增模态框关闭的处理函数，也顺带处理了新增成功后的逻辑
    hanldeUpdateModalClose, // 更新模态框关闭的处理函数，也顺带处理了更新成功后的逻辑
}=useTableMixin({
	columns,
	listApiFunc: routeList.getPageList,
	deleteApiFunc: routeList.deleteItem,
	actionList: [actionKeys.update, actionKeys.delete],
    setTableHeightExtendParams:{tHeaderHeight: 77},
	searchPanelcollapsed_after: (h) => {
		setTableHeight({tableHeightRef: treeHeight,otherSectionHeight: 52 + h,isTable: false})
	},
	add_before: () => {
		if (!selectedKeys.value.length) {
			message.warning('请先在左侧树选择父节点')
			return
		}
		if (selectedNode.value.component) {
			message.warning('选中的是叶子节点，不可添加子路由')
			return
		}
		if (selectedNode.value.link) {
			message.warning('选中的是外部链接，不可添加子路由')
			return
		}
		return true
	},
	update_before: () => {
		return true
	},
	delete_before: () => {
		return true
	},
	add_after: () => {
		getTreeData()
	},
	delete_after: () => {
		if(editRow.value.name==selectedNode.value.name){
			selectedNode.value = {} as routeTreeNode
	    selectedKeys.value.pop() 
		}
		getTreeData()
	},
	query_after: () => {},
	update_after: () => {
		getTreeData()
	},
	search_after: () => {},
	reset_after: () => {
		selectedNode.value={} as routeTreeNode
		selectedKeys.value.pop()
	},
})

onBeforeMount(() => {
	getTreeData()
})


// 页面内函数统一使用function，箭头函数不能提升，书写顺序上有一定局限性


async function getTreeData() {
  const res = await routeList.getList()
	if (res.code) {
		const tree = listToTree<routeTreeNode>(res.list, 'id', 'pId', false, (i) => {
		if (i.component || i.link) i.style = { color: primaryColor_hex }
	},(j=>{hasChildKeys.value.add(j.name)})) as routeTreeNode
	// console.log(tree,[...list])
	treeData.value = sortTreeArr([tree],'rank')
	// console.log([...hasChildKeys.value])
	// console.log(tree)
	}
	
}




function handleSelectTreeNode(selectedKeys: any, e: any) {
	//  console.log(selectedKeys,e)
	if (selectedKeys[0]) {
		selectedNode.value = e.node.dataRef
		filterOptions.value={name:selectedNode.value.name}
		getData()
	} else {
		selectedNode.value = {} as routeTreeNode
	}
	//console.log({...selectedNode.value})
}

</script>

<template>
	<div class="routeManage">
		<search-panel @collapsed="handleSearchPanelcollapsed" @search="handleSearch" @reset="handleReset" :options="searchOptions" />
		<div class="container" style="display: flex">
			<div class="left" :style="{ height: treeHeight + 'px' }">
				<a-tree
					:fieldNames="{ children: 'children', title: 'title', key: 'name' }"
					v-model:expandedKeys="expandedKeys"
					v-model:selectedKeys="selectedKeys"
					:treeData="treeData"
					@select="handleSelectTreeNode"
				/>
			</div>
			<div class="bar" :style="{ height: treeHeight + 'px' }"></div>
			<div class="right">
				<div class="tableTool">
					<a-button type="primary" style="margin-right: 5px" @click="handleAdd" v-if="$hasAuth([actionKeys.add])">新增子路由</a-button>
					<tableColSetting :list="columns" :fixedColWidth="fixedColWidth" @confirm="handleColumnsChange" />
				</div>

				<!-- 'max-content':保证每一列完整显示 -->
				<a-table
					:dataSource="tableList"
					:columns="columns"
					size="small"
					style="width: 100%"
					class="myTable"
					rowKey="name"
					:scroll="{ x: '100%', y: tableHeight }"
					:pagination="{
						current,pageSize:size,total,
						showSizeChanger:true ,showQuickJumper:true,showTotal:(t:any,r:any)=>`共${t}条`,
						onChange:(page:number,size:number)=>{handlePaginationChange({page,size})}
					}"
				>
					<template #bodyCell="{ record, column }: any">
						<template v-if="column.key === 'operation'">
							<a-button type="primary" size="small" @click="handleUpdate(record)" style="margin-right: 5px" v-if="$hasAuth([actionKeys.update])" :disabled="record.name==layoutRouteName">修改</a-button>
							<a-popconfirm
								title="确定要删除吗?"
								ok-text="确定"
								cancel-text="取消"
								@confirm="handleDelete(record)"
								placement="topLeft"
								:disabled="[...hasChildKeys].includes(record.name)"
								v-if="$hasAuth([actionKeys.delete])"
							>
								<!-- 后方没按钮就不写外边距，否则按钮的排列会不居中 -->
								<a-button type="danger" size="small" :disabled="[...hasChildKeys].includes(record.name)" style="margin-right: 0px">删除</a-button>
							</a-popconfirm>
						</template>
					</template>
				</a-table>
			</div>
		</div>

		<Add :visible="addModalVisible" :parentNode="(selectedNode as any)" @close="hanldeAddModalClose" />

		<Update :visible="updateModalVisible" :editNode="(editRow as any)" @close="hanldeUpdateModalClose" />
	</div>
</template>

<style scoped lang="less">
.routeManage {
	.container {
		.left {
			overflow: hidden auto;
			margin-top: 52px;
			background-color: white;
			width: 180px;
			flex-shrink: 0;
		}
		.bar {
			width: 5px;
			background-color: gainsboro;
			margin: 52px 0 0 10px;
			background-clip: content-box;
			padding: 0 2px;
			flex-shrink: 0;
		}
		.right {
			padding-left: 20px;
			width: calc(100% - 180px - 15px);
		}
	}

	.tableTool {
		padding: 10px 0;
		display: flex;
		justify-content: flex-end;
		align-items: center;
	}

	:deep(.ant-tree-node-content-wrapper) {
		white-space: nowrap;
	}
}
</style>
